springcloud --客户端负载均衡:spring cloud ribbon-LoadBalancer简单分析

通过我之前的RestTemplate简单分析可以知道,虽然spring cloud 之中定义了LoadBalancerClient作为负载均衡的通用接口,并且对于Ribbon有了具体的实现RibbonLoadBalancerClient,但是,在具体使用客户端负载均衡时是使用Ribbon的ILoadBalancer接口实现的,现在我就根据ILoadBalancer接口的实现类来具体的分析分析。

AbstractLoadBalancer

AbstractLoadBalancer是ILoadBalancer的抽象实现,定义了关于服务器分组的枚举类ServerGroup,三种不同类型

 public enum ServerGroup{
        ALL,//所有服务实例
        STATUS_UP,//正常服务的实例
        STATUS_NOT_UP//停止服务的实例        
    }

还有一个chooseServer()方法,即调用接口的chooseServer(Object key)方法,表示在选择服务实例的时候忽略key条件判断。除此之外,还定义了两个抽象函数

  • List<Server> getServerList(ServerGroup serverGroup):根据服务分组获取对应的服务实例列表
  • LoadBalancerStats getLoadBalancerStats():定义了获取LoadBalancerStats的方法

下面,贴出具体源码

public abstract class AbstractLoadBalancer implements ILoadBalancer {
    
    public enum ServerGroup{
        ALL,
        STATUS_UP,
        STATUS_NOT_UP        
    }
        
    public Server chooseServer() {
    	return chooseServer(null);
    }

    public abstract List<Server> getServerList(ServerGroup serverGroup);

    public abstract LoadBalancerStats getLoadBalancerStats();    
}

具体的类结构

 首先看 BaseLoadBalancer

BaseLoadBalancer是Ribbon负载均衡的基础实现类,定义了很多的基础概念

  • addServers(List<Server> newServers) 实现,向负载均衡中增加新的 服务实例列表;将所有的服务实例假如到newServers中,然后调用setServersList方法对newList处理,负载均衡的扩展类一般都是通过对setServersList方法重写来实现的
    public void addServers(List<Server> newServers) {
            if (newServers != null && newServers.size() > 0) {
                try {
                    ArrayList<Server> newList = new ArrayList<Server>();
                    newList.addAll(allServerList);
                    newList.addAll(newServers);
                    setServersList(newList);
                } catch (Exception e) {
                    logger.error("LoadBalancer [{}]: Exception while adding Servers", name, e);
                }
            }
        }

     

  • markServerDown(Server server):标记服务处于暂停状态
    public void markServerDown(Server server) {
            if (server == null || !server.isAlive()) {
                return;
            }
    
            logger.error("LoadBalancer [{}]:  markServerDown called on [{}]", name, server.getId());
            server.setAlive(false);
            // forceQuickPing();
    
            notifyServerStatusChangeListener(singleton(server));
        }

     

  • getReachableServers():获取可用的服务列表
    public List<Server> getReachableServers() {
            return Collections.unmodifiableList(upServerList);
        }

     

  • List<Server> getAllServers():获取所有服务列表
    public List<Server> getAllServers() {
            return Collections.unmodifiableList(allServerList);
        }

     

  • 两个维护服务实例server对象的列表,一个用于存储所有服务实例的清单,另一个用于存储正常服务的实例清单
     @Monitor(name = PREFIX + "AllServerList", type = DataSourceType.INFORMATIONAL)
        protected volatile List<Server> allServerList = Collections
                .synchronizedList(new ArrayList<Server>());
        @Monitor(name = PREFIX + "UpServerList", type = DataSourceType.INFORMATIONAL)
        protected volatile List<Server> upServerList = Collections
                .synchronizedList(new ArrayList<Server>());

     

  • 定义了心跳检测的IPing对象,默认为null,在构造方法里传入
     

        protected IPing ping = null;

     

  • 定义了心跳检测的执行策略对象IPingStrategy,默认使用的是SerialPingStrategy,该策略使用的是线性遍历ping服务实例的方式检测。当IPing的速度慢,或是Server列表过大的时候,就会影响性能了。
     

     private static class SerialPingStrategy implements IPingStrategy {
    
            @Override
            public boolean[] pingServers(IPing ping, Server[] servers) {
                int numCandidates = servers.length;
                boolean[] results = new boolean[numCandidates];
    
          
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值